package utils;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.node.ObjectNode;
import com.fasterxml.jackson.datatype.joda.JodaMapper;
import org.apache.commons.lang.StringUtils;
import org.json.JSONException;
import org.json.JSONObject;

import java.io.IOException;


/**
 * Created by kzdatd on 2020/1/13.
 */
public class JSONUtil {

    private static JodaMapper getJodaMapper() {
        JodaMapper jodaMapper = new JodaMapper();
        jodaMapper.setWriteDatesAsTimestamps(false);
        return jodaMapper;
    }

    public static JsonNode StrToJsonNode(String jsonString) {
        try {
            return getJodaMapper().readTree(jsonString);
        } catch (IOException e) {

        }
        return null;
    }

    public static <T> Object JsonToObj(String jsonStr, Class<T> obj) {
        T t = null;
        try {
            JodaMapper objectMapper = getJodaMapper();
            t = objectMapper.readValue(jsonStr, obj);
        } catch (Exception e) {

        }
        return t;
    }

    public static <T> JSONObject objectToJson(T obj) throws JSONException, IOException {
        JodaMapper objectMapper = getJodaMapper();
        String jsonStr = "";
        try {
            jsonStr = objectMapper.writeValueAsString(obj);
        } catch (JsonProcessingException e) {
            e.printStackTrace();
        }
        return new JSONObject(jsonStr);
    }

    public static <T> String objectToStr(T obj) throws JSONException, IOException {
        JodaMapper objectMapper = getJodaMapper();
        String jsonStr = "";
        try {
            jsonStr = objectMapper.writeValueAsString(obj);
        } catch (JsonProcessingException e) {
            e.printStackTrace();
        }
        return jsonStr;
    }

    public static <T> ObjectNode convertObject2ObjectNode(T object)
            throws Exception {
        if (null == object) {
            return null;
        }

        ObjectNode objectNode = null;

        if (object instanceof String) {
            objectNode = convertJsonStringToObject((String) object,
                    ObjectNode.class);
        } else {
            objectNode = convertValue(object, ObjectNode.class);
        }

        return objectNode;
    }

    /**
     * Method that will convert the json string to destination by the type(cls).
     *
     * @param jsonString
     *            the source json string; if null, will return null.
     * @param cls
     *            the destination data type.
     */
    public static <T> T convertJsonStringToObject(String jsonString,
                                                  Class<T> cls) throws Exception {
        if (StringUtils.isEmpty(jsonString)) {
            return null;
        }

        try {
            T object = getJodaMapper().readValue(jsonString, cls);
            return object;
        } catch (Exception e) {
            throw new Exception(e);
        }
    }

    /**
     * Method that will convert from given value into instance of given value
     * type.
     *
     */
    private static <T> T convertValue(Object fromValue, Class<T> toValueType)
            throws Exception {
        try {
            return getJodaMapper().convertValue(fromValue, toValueType);
        } catch (IllegalArgumentException e) {
            throw new Exception(e);
        }
    }
}
